package com.itheima.filter;

import com.alibaba.fastjson.JSONObject;
import com.itheima.pojo.Result;
import com.itheima.utils.JwtUtils;
import lombok.extern.slf4j.Slf4j;

import javax.servlet.*;
import javax.servlet.annotation.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;


@WebFilter("/*")
@Slf4j
public class LoginFilter implements Filter {

/**
     * 对 所有的请求都进行拦截
     * @param req   拦截请求对象 ServletRequest 有个儿子遵循http协议 HttpServletRequest
     * @param resp  拦截响应对象 ServletResponse   HttpServletResponse
     * @param chain   用来 完成放行与否的 保安
     * @throws ServletException
     * @throws IOException
     */

    /**
     *
     * @author :速趴赛亚锦=====================================【过滤器拦截住 所有的资源】
     * @create :2024/03/18 16:10
     */

    @Override
    public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException {

/*
           问 所有的请求  都要验证令牌吗？
                登录不需要  如果是登录请求 就直接放行！！！
           问 拦截请求之后，什么情况下才可以放行  去执行对应的业务
              有令牌
              且令牌通过校验

              否则都是 未登录 返回 一个
                      {
                       "code":0,
                       "msg":"NOT_LOGIN",
                        "data":null
                      }
                 是Result.error("NOT_LOGIN")      json格式！
         */

        //0: 前置操作因为解析过程中要使用  HttpServletRequest 子接口中的方法
        //   所以需要进行向下转型(还原类型)
        HttpServletRequest request = (HttpServletRequest)req;
        HttpServletResponse response = (HttpServletResponse)resp;

        //1:通过请求对象获取请求路径
        String url = request.getRequestURL().toString();
        log.info("请求路径:{}",url);
        //2:判断 url是否是 登录请求 如果是就放行
        if(url.contains("/login")){
            log.info("是登录请求，可以放行");
            chain.doFilter(request, response);
            return;//结束当前方法 已经完成了
        }
        //3:不是登录请求 获取请求头 token数据
        String token = request.getHeader("token");
        log.info("获取令牌数据:{}",token);

        //4: 判断令牌 是不是存在
        if(token==null||token.length()==0){//是空的
             log.info("令牌不存在");
             //  完成  响应操作 响应 Result.error("NOT_LOGIN")
            // 不能直接return Result
            // 因为这个技术 是 web的技术 不是 spring技术
            // a先封装对象
            Result result = Result.error("NOT_LOGIN");
            // b 把这个 对象转换json!!手动转换  因为这不是spring框架
            // 需要借助一个 json转换包
            String json = JSONObject.toJSONString(result);
            // 因为设置的数据是json格式 还要告知浏览器是json数据
            response.setContentType("application/json;charset=utf-8");// 告知浏览数据格式
            // c: 把json字符串 设置到响应体中
            response.getWriter().write(json);//
            return;
        }
        //5:有token 解析  有异常就是解析失败
        try{
             JwtUtils.parseJWT(token);
        }catch (Exception e){
            log.info("解析失败");
            // a先封装对象
            Result result = Result.error("NOT_LOGIN");
            // b 把这个 对象转换json!!手动转换  因为这不是spring框架
            // 需要借助一个 json转换包
            String json = JSONObject.toJSONString(result);
            // 因为设置的数据是json格式 还要告知浏览器是json数据
            response.setContentType("application/json;charset=utf-8");// 告知浏览数据格式
            // c: 把json字符串 设置到响应体中
            response.getWriter().write(json);//
            return;
        }
        //token是对的 就放行
        chain.doFilter(request, response);

    }

    public void init(FilterConfig config) throws ServletException {
    }

    public void destroy() {
    }

}
